Skip to content

chore: enforce awaiting promises by lint - #2863

Open
minottic wants to merge 2 commits into
masterfrom
enforce_awit
Open

chore: enforce awaiting promises by lint#2863
minottic wants to merge 2 commits into
masterfrom
enforce_awit

Conversation

@minottic

@minottic minottic commented Jul 31, 2026

Copy link
Copy Markdown
Member

Description

Guard against un-awaited promises when linting

Motivation

Good practice to prevent messed up resolution order

Summary by Sourcery

Enforce proper awaiting of asynchronous operations across the codebase and configure linting rules to guard against unhandled promises.

Enhancements:

  • Refactor access group service factory to use async/await for dynamic GraphQL response processor imports.
  • Ensure user role creation for multiple users awaits all role assignment operations using Promise.all.
  • Handle potential initialization failures in the Opensearch module by logging unexpected errors instead of allowing unhandled promise rejections.
  • Await default policy creation in the datasets module to ensure policies are created before continuing module initialization.
  • Adjust logout handling to avoid passing an async callback to the Express logout function.

Build:

  • Enable ESLint rules to disallow floating and misused promises in the TypeScript configuration.

@minottic
minottic requested a review from a team as a code owner July 31, 2026 16:58
@minottic minottic mentioned this pull request Jul 31, 2026
4 tasks

@sourcery-ai sourcery-ai Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Hey - I've found 2 issues, and left some high level feedback:

  • The async accessGroupServiceFactory.useFactory now awaits a dynamic import without any error handling; consider wrapping the import and service construction in a try/catch so misconfigured responseProcessorSrc doesn’t break module initialization silently.
  • In datasets.module.ts, await policyService.addDefaultPolicy(...) assumes the surrounding context is async; double-check that the enclosing function is marked async or otherwise explicitly handles the returned promise to avoid runtime/TypeScript issues.
Prompt for AI Agents
Please address the comments from this code review:

## Overall Comments
- The async `accessGroupServiceFactory.useFactory` now awaits a dynamic import without any error handling; consider wrapping the import and service construction in a try/catch so misconfigured `responseProcessorSrc` doesn’t break module initialization silently.
- In `datasets.module.ts`, `await policyService.addDefaultPolicy(...)` assumes the surrounding context is async; double-check that the enclosing function is marked `async` or otherwise explicitly handles the returned promise to avoid runtime/TypeScript issues.

## Individual Comments

### Comment 1
<location path="src/opensearch/opensearch.service.ts" line_range="76-81" />
<code_context>

   onModuleInit() {
-    this.initWithRetry();
+    this.initWithRetry().catch((error) => {
+      Logger.error(
+        "Opensearch initialization failed unexpectedly",
+        error,
+        "Opensearch",
+      );
+    });
   }
</code_context>
<issue_to_address>
**question (bug_risk):** Catching initialization errors here prevents module init from failing; verify this aligns with desired failure semantics and health reporting.

Because the error is only logged, `onModuleInit` succeeds even when Opensearch is down, so the service can start with a broken search subsystem. If Opensearch is required for correct operation, consider rethrowing after logging or wiring this failure into your readiness/health checks so the service is marked not-ready when initialization fails.
</issue_to_address>

### Comment 2
<location path="eslint.config.mjs" line_range="58-59" />
<code_context>

       "@typescript-eslint/no-explicit-any": "error",
       "@typescript-eslint/no-inferrable-types": "error",
+      "@typescript-eslint/no-floating-promises": "error",
+      "@typescript-eslint/no-misused-promises": "error",

       quotes: [
</code_context>
<issue_to_address>
**suggestion:** Enabling strict promise rules globally can cause friction in framework callbacks; consider scoping or adding targeted overrides.

In Nest/Express there are common patterns (event handlers, middleware, lifecycle hooks) where async functions or returned promises are expected and harmless. Please check whether these rules create noisy violations in those areas and, if so, consider scoping them (per folder/file) so you keep the safety benefits without fighting the framework’s patterns.

Suggested implementation:

```javascript
      "@typescript-eslint/no-explicit-any": "error",
      "@typescript-eslint/no-inferrable-types": "error",
      // Promise rules are warnings by default to avoid friction in framework callbacks;
      // stricter enforcement is applied via targeted overrides.
      "@typescript-eslint/no-floating-promises": "warn",
      "@typescript-eslint/no-misused-promises": "warn",

      quotes: [
        "error",

```

To fully implement the scoping behavior you described, add or extend an `overrides` section in `eslint.config.mjs` such as:

- For general app code (e.g. `src/**/*.ts`, excluding framework-specific folders):
  - Set `@typescript-eslint/no-floating-promises` and `@typescript-eslint/no-misused-promises` back to `"error"`.

- For framework-heavy areas (adjust paths to match your project layout, examples):
  - `src/**/middleware/**/*.ts`
  - `src/**/interceptors/**/*.ts`
  - `src/**/guards/**/*.ts`
  - `src/**/filters/**/*.ts`
  - `src/**/listeners/**/*.ts`
  - `src/**/subscribers/**/*.ts`
  - `src/**/events/**/*.ts`
  In those overrides, either:
  - Keep these rules at `"warn"`, or
  - Configure them more leniently (e.g. `@typescript-eslint/no-misused-promises` with `checksVoidReturn: false` for callbacks).

You’ll need to tailor the `files` globs in `overrides` to your actual Nest/Express folder structure to ensure that normal request-handling/business logic gets strict promise checks, while middleware and lifecycle hooks avoid noisy, low-value violations.
</issue_to_address>

Sourcery is free for open source - if you like our reviews please consider sharing them ✨
Help me be more useful! Please click 👍 or 👎 on each comment and I'll use the feedback to improve your reviews.

Comment thread src/opensearch/opensearch.service.ts
Comment thread eslint.config.mjs
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants